#include "var.h"
using namespace sge;

Var::Var() :
    dirty(false),
    type(BOOL) {
}

Var::~Var() {
    if (type == STRING) {
        delete data.s;
        data.s = 0;
    } else if (type == VECTOR) {
        delete data.v;
        data.v = 0;
    } else if (type == QUATERNION) {
        delete data.q;
        data.q = 0;
    }
    
    type = BOOL;
}

VarType Var::getVarType() const {
    return type;
}

void Var::setVarType(VarType _type) {
    if (type != _type) {
        if (type == STRING) {
            delete data.s;
            data.s = 0;
        } else if (type == VECTOR) {
            delete data.v;
            data.v = 0;
        } else if (type == QUATERNION) {
            delete data.q;
            data.q = 0;
        }
    
        type = _type;
        if (type == STRING) {
            data.s = new String;
        } else if (type == VECTOR) {
            data.v = new Vector3;
        } else if (type == QUATERNION) {
            data.q = new Quaternion;
        }
    }
}

bool Var::getB() {
    setVarType(BOOL);
    return data.b;
}

int Var::getI() {
    if (type == FLOAT)
        return int(data.f);
    setVarType(INT);
    return data.i;
}

float Var::getF() {
    if (type == INT)
        return float(data.i);
    setVarType(FLOAT);
    return data.f;
}

String Var::getS() {
    setVarType(STRING);
    return *data.s;
}

Vector3 Var::getV() {
    setVarType(VECTOR);
    return *data.v;
}

Quaternion Var::getQ() {
    setVarType(QUATERNION);
    return *data.q;
}

void Var::setB(bool b) {
    setVarType(BOOL);
    data.b = b;
    dirty = true;
}

void Var::setI(int i) {
    setVarType(INT);
    data.i = i;
    dirty = true;
}

void Var::setF(float f) {
    setVarType(FLOAT);
    data.f = f;
    dirty = true;
}

void Var::setS(String s) {
    setVarType(STRING);
    *data.s = s;
    dirty = true;
}

void Var::setV(Vector3 v) {
    setVarType(VECTOR);
    *data.v = v;
    dirty = true;
}

void Var::setQ(Quaternion q) {
    setVarType(QUATERNION);
    *data.q = q;
    dirty = true;
}

bool Var::getDirty() const {
    return dirty;
}

void Var::setDirty(bool _dirty) {
    dirty = _dirty;
}
